<template>
  <el-upload
    v-model:file-list="innerFileList"
    v-bind="uploadProps"
    :class="{'fancy-upload': true, 'drag-mode': conf.dragUpload}"
    @change="handleChange"
    @preview="handlePreview"
    @remove="handleRemove"
  >
    <template v-if="conf['list-type'] === 'text'">
      <el-button type="primary">
        <!-- <el-icon><Upload /></el-icon> -->
        {{ conf.buttonText || '上传文件' }}
      </el-button>
      <!-- <template #tip v-if="conf.showTip">
        <div class="el-upload__tip">{{ conf.tips }}</div>
      </template> -->
    </template>

    <template v-else-if="conf['list-type'] === 'picture-card'">
      <icon :code="'input'"></icon>
      <!-- <el-icon><Plus /></el-icon> -->
      <div class="preview-thumbnail" v-if="previewUrl">
        <img :src="previewUrl" />
      </div>
    </template>

    <template #drag v-if="conf.dragUpload">
      <!-- <el-icon class="el-icon--upload"><UploadFilled /></el-icon> -->
      <div class="el-upload__text">
        将文件拖到此处，或<em>点击上传</em>
      </div>
    </template>
  </el-upload>

  <el-dialog v-model="previewVisible" title="文件预览" width="70%">
    <img v-if="isImage(previewFile)" :src="previewFile.url" class="preview-image" />
    <div v-else class="file-preview">
      <!-- <el-icon :size="50"><Document /></el-icon> -->
      <p>{{ previewFile.name }}</p>
      <el-button type="primary" @click="downloadFile(previewFile)">
        下载文件 ({{ formatFileSize(previewFile.size) }})
      </el-button>
    </div>
  </el-dialog>
</template>

<script setup>
import { ref, computed } from 'vue'
// import { Upload, Plus, UploadFilled, Document } from '@element-plus/icons-vue'
import icon from '@/components/formDesigner/icon.vue'
import { ElMessage } from 'element-plus'

const props = defineProps({
  conf: {
    type: Object,
    required: true
  },
  modelValue: {
    type: Array,
    default: () => []
  }
})

const emit = defineEmits(['update:modelValue', 'file-change'])

const innerFileList = ref(props.modelValue)
const previewVisible = ref(false)
const previewFile = ref(null)
const previewUrl = ref('')

const uploadProps = computed(() => ({
  action: props.conf.action,
  multiple: props.conf.multiple,
  accept: props.conf.accept,
  'list-type': props.conf['list-type'],
  'show-file-list': props.conf['show-file-list'],
  drag: props.conf.dragUpload,
  limit: props.conf.maxCount,
  'on-exceed': handleExceed,
  'before-upload': beforeUpload
}))

const isImage = (file) => file?.type?.includes('image') || 
  ['.jpg', '.jpeg', '.png', '.gif'].some(ext => file.name.endsWith(ext))

const formatFileSize = (bytes) => {
  if (!bytes) return '0 B'
  const units = ['B', 'KB', 'MB', 'GB']
  let size = bytes
  let unitIndex = 0
  while (size >= 1024 && unitIndex < units.length - 1) {
    size /= 1024
    unitIndex++
  }
  return `${size.toFixed(2)} ${units[unitIndex]}`
}

const beforeUpload = (file) => {
  // 文件类型校验
  const validTypes = props.conf.accept.split(',')
    .map(ext => ext.trim().toLowerCase())
  
  const isValid = validTypes.some(type => 
    type.startsWith('.') 
      ? file.name.toLowerCase().endsWith(type)
      : file.type.includes(type.replace('/*', ''))
  )

  if (!isValid) {
    ElMessage.error(`仅支持 ${props.conf.accept} 格式的文件`)
    return false
  }

  // 文件大小校验
  if (file.size > props.conf.fileSize * 1024 * 1024) {
    ElMessage.error(`文件大小不能超过 ${props.conf.fileSize}MB`)
    return false
  }

  // 图片预览处理
  if (isImage(file)) {
    const reader = new FileReader()
    reader.onload = (e) => {
      previewUrl.value = e.target.result
    }
    reader.readAsDataURL(file)
  }

  return true
}

const handleChange = (file, fileList) => {
  innerFileList.value = fileList
  emit('update:modelValue', fileList)
  emit('file-change', fileList)
}

const handlePreview = (file) => {
  previewFile.value = file
  previewVisible.value = true
}

const handleRemove = (file) => {
  innerFileList.value = innerFileList.value.filter(f => f.uid !== file.uid)
  emit('update:modelValue', innerFileList.value)
}

const handleExceed = () => {
  ElMessage.warning(`最多只能上传 ${props.conf.maxCount} 个文件`)
}

const downloadFile = (file) => {
  const link = document.createElement('a')
  link.href = file.url
  link.download = file.name
  link.click()
}
</script>

<style scoped>
.fancy-upload {
  width: 100%;
}

.drag-mode {
  padding: 20px;
  border: 1px dashed var(--el-border-color);
  border-radius: 6px;
}

.preview-thumbnail {
  margin-top: 8px;
}
.preview-thumbnail img {
  max-width: 100%;
  max-height: 100px;
  object-fit: contain;
}

.preview-image {
  max-width: 100%;
  max-height: 70vh;
  display: block;
  margin: 0 auto;
}

.file-preview {
  text-align: center;
  padding: 20px;
}
.file-preview .el-icon {
  color: var(--el-color-primary);
  margin-bottom: 10px;
}
</style>